home *** CD-ROM | disk | FTP | other *** search
/ Collection of Tools & Utilities / Collection of Tools and Utilities.iso / asmutil / asm_n_z.zip / STATLINE.ASM < prev    next >
Assembly Source File  |  1986-04-17  |  13KB  |  349 lines

  1. ;-----------------------------------------------------------------------;
  2. ; STATLINE, by John Socha, Copyright 1986 Ziff-Davis Publishing Co.    ;
  3. ;                                    ;
  4. ; Here are the two interrupt vectors that we take over.  The first    ;
  5. ; interrupt, INT 9, is the hardware interrupt for the keyboard, and    ;
  6. ; it's called every time you push or release a key.            ;
  7. ;                                    ;
  8. ; The other interrupt, INT 10h, points to the ROM BIOS routines that    ;
  9. ; handle all of the screen I/O.  We intercept it so that we can watch    ;
  10. ; for commands to change the display mode.  Since STATLINE only works    ;
  11. ; in 80x25 text modes, STATLINE turns itself off as long as the screen    ;
  12. ; is in a different mode.                        ;
  13. ;-----------------------------------------------------------------------;
  14. VECTORS        SEGMENT AT 0h
  15.     ORG    9h*4
  16. KEYBOARD_INT_VECTOR    LABEL    DWORD    ;Keyboard interrupt
  17.     ORG    10h*4
  18. VIDEO_IO_VECTOR        LABEL    DWORD    ;ROM BIOS Video I/O function calls
  19. VECTORS        ENDS
  20.  
  21.  
  22. ;-----------------------------------------------------------------------;
  23. ; STATLINE uses the following flags from the ROM BIOS's data area to    ;
  24. ; control the screen.                            ;
  25. ;-----------------------------------------------------------------------;
  26. ROM_BIOS_DATA    SEGMENT AT 40h
  27.     ORG    10h
  28. EQUIP_FLAG    DB    ?        ;Equipment installed
  29.     ORG    17h
  30. KBD_FLAG    DB    ?        ;Used to determine display type
  31.     ORG    4Eh
  32. CRT_START    DW    ?        ;Starting address in buffer
  33.     ORG    63h
  34. ADDR_6845    DW    ?        ;3x8 register, where x is B or D
  35. ROM_BIOS_DATA    ENDS
  36.  
  37.  
  38. ;-----------------------------------------------------------------------;
  39. ; This section of the ROM in a COMPAQ contains the 6 bytes 'COMPAQ'    ;
  40. ; which we can use to identify a COMPAQ computer.  COMPAQ computers    ;
  41. ; have a display adapter that uses the monochrome display, but with    ;
  42. ; registers and memory the same as a color graphics adapter.        ;
  43. ;-----------------------------------------------------------------------;
  44. COMPAQ_CO    EQU    4F43h        ;ASCII code of 'CO'
  45.  
  46. COMPAQ_SEG    SEGMENT AT 0F000h
  47.     ORG    0FFEAh
  48. COMPAQ_ID    DW    ?        ;We should find 'CO' (4F43h) here
  49. COMPAQ_SEG    ENDS
  50.  
  51.  
  52. ;-----------------------------------------------------------------------;
  53. ; Here is the STATLINE's entry point.  It jumps to the initialization    ;
  54. ; routine which is at the very end so that we can throw it out of    ;
  55. ; memory after we've used it.                        ;
  56. ;-----------------------------------------------------------------------;
  57. CODE_SEG    SEGMENT
  58.     ASSUME    CS:CODE_SEG, DS:CODE_SEG
  59.     ORG    100h        ;Reserve for DOS Program Segment Prefix
  60. BEGIN:    JMP    INIT_VECTORS
  61.  
  62. AUTHOR_STRING        DB    "Installed Statline, by John Socha"
  63.             DB    0Dh, 0Ah, '$'
  64.  
  65. OLD_KBD_FLAG        DB    0    ;Most recent upper nibble of status
  66. VIDEO_MODE        DB    ?    ;Current video mode
  67. STATUS_LINE_ENABLED    DB    1    ;0 when we're in graphics modes
  68.  
  69. ;-----------------------------------------------------------------------;
  70. ; The following table contains the character/attribute pairs for the    ;
  71. ; states of the Scroll Lock, Num Lock, and Caps Lock keys.        ;
  72. ;                                    ;
  73. ; The first word contains the address for the character, and the second    ;
  74. ; word contains the character/attribute pair.                ;
  75. ;-----------------------------------------------------------------------;
  76. ENTRY    STRUC
  77. OFFSET_FROM_TOP        DW    ?    ;Offset from start of display memory
  78. ATTRIBUTE_CHARACTER    DB    ?    ;Attribute and character code
  79. ENTRY    ENDS
  80.  
  81. FLAG_CHARACTER_TABLE    LABEL    WORD
  82.     ENTRY    <4084,' '>        ;Scroll Lock, ' '
  83.     ENTRY    <4084,12h>        ;Scroll Lock, double-ended arrow
  84.     ENTRY    <4080,' '>        ;Num Lock, ' '
  85.     ENTRY    <4080,23h>        ;Num lock, '#'
  86.     ENTRY    <4076,' '>        ;Caps Lock, ' '
  87.     ENTRY    <4076,18h>        ;Caps Lock, up arrow
  88.  
  89. ROM_KEYBOARD_INT    DD    ?
  90. ROM_VIDEO_IO_INT    DD    ?
  91.  
  92. ;-----------------------------------------------------------------------;
  93. ; This procedure sends control off to the ROM BIOS routine, then checks    ;
  94. ; the shift-lock flags on return and writes the new flag characters to    ;
  95. ; the screen.                                ;
  96. ;-----------------------------------------------------------------------;
  97. INTERCEPT_KEYBOARD_INT    PROC    FAR
  98.     ASSUME    CS:CODE_SEG, DS:NOTHING
  99.     PUSHF                ;Simulate INT with PUSHF and CALL
  100.     CALL    ROM_KEYBOARD_INT    ;Let ROM do the work
  101.     CMP    STATUS_LINE_ENABLED,1    ;See if Status line enabled.
  102.     JNE    NO_STATUS_LINE        ;Not enabled.
  103.     CALL    CHECK_STATUS_FLAGS    ;Check flags and update status line
  104. NO_STATUS_LINE:
  105.     IRET
  106. INTERCEPT_KEYBOARD_INT    ENDP
  107.  
  108.  
  109. ;-----------------------------------------------------------------------;
  110. ; This procedure checks the current setting of KBD_FLAGS against the    ;
  111. ; last setting, and if the flags have changed, it updates the status    ;
  112. ; line display.  Check_status_flags also updates Old_kbd_flag.        ;
  113. ;-----------------------------------------------------------------------;
  114. CHECK_STATUS_FLAGS    PROC    NEAR
  115.     PUSH    AX            ;Save all the registers we use
  116.     PUSH    BX
  117.     PUSH    CX
  118.     PUSH    DX
  119.     PUSH    SI
  120.     PUSH    DI
  121.     PUSH    DS
  122.     PUSH    ES
  123.     ASSUME    CS:CODE_SEG, DS:ROM_BIOS_DATA
  124.     MOV    AX,ROM_BIOS_DATA    ;Set DS so it points to BIOS data area
  125.     MOV    DS,AX
  126.     MOV    DX,ADDR_6845        ;Get the base address for the 6845
  127.     MOV    AX,0B800h        ;Segment address of graphics adapter
  128.     CMP    DX,3D0h            ;Is this the color graphics adapter?
  129.     JAE    IS_COLOR_BOARD      ;It's a color board, so don't change AX
  130.     MOV    AX,0B000h           ;Segment address for monochrome adapter
  131. IS_COLOR_BOARD:
  132.     MOV    ES,AX            ;Use extra segment for display memory
  133.  
  134.     ADD    DX,03DAh-03D4h        ;Point to status register
  135.     MOV    BL,KBD_FLAG        ;Get flag information
  136.     MOV    CL,4                ;Put shift lock flags into lower nibble
  137.     SHR    BL,CL
  138.     ASSUME    CS:CODE_SEG, DS:CODE_SEG
  139.     MOV    AX,CS            ;Set DS to the local data (in CS)
  140.     MOV    DS,AX
  141.     CMP    BL,OLD_KBD_FLAG        ;Have any of the status flags changed?
  142.     JE    FLAGS_HAVENT_CHANGED    ;No, then do nothing
  143.     MOV    OLD_KBD_FLAG,BL        ;Flags have changed, update status line
  144.     MOV    SI,Offset FLAG_CHARACTER_TABLE
  145.  
  146.     MOV    CX,3            ;Repeat for three shift lock keys
  147. SHIFT_LOCK_LOOP:
  148.     PUSH    SI
  149.     SHR    BL,1            ;Get next flag in carry
  150.     JNC    READ_OFFSET        ;Flag was 0, SI Ok
  151.     ADD    SI,3            ;Skip over information
  152. READ_OFFSET:
  153.     MOV    DI,[SI]            ;Get Offset
  154.     MOV    AL,[SI+2]        ;Get character for this flag
  155.     
  156.     PUSH    CX            ;Save the CX register
  157.     MOV    CL,AL            ;Save the character in CL
  158. WAIT_FOR_NON_RETRACE:
  159.     IN    AL,DX            ;Read status
  160.     TEST    AL,8            ;In vertical retrace?
  161.     JNZ    WAIT_FOR_NON_RETRACE    ;Wait for vertical retrace to finish
  162. WAIT_FOR_RETRACE:
  163.     IN    AL,DX            ;Read status
  164.     TEST    AL,8            ;In vertical retrace?
  165.     JZ    WAIT_FOR_RETRACE    ;No, then wait for vertical retrace
  166.     MOV    AL,CL            ;Get the character we want to write
  167.     STOSB                ;Write character to the screen
  168.     POP    CX            ;Recover the old value of CX
  169.  
  170.     POP    SI
  171.     ADD    SI,6            ;Skip to next pair of entries
  172.     LOOP    SHIFT_LOCK_LOOP
  173.  
  174. FLAGS_HAVENT_CHANGED:
  175.     POP    ES
  176.     POP    DS
  177.     POP    DI
  178.     POP    SI
  179.     POP    DX
  180.     POP    CX
  181.     POP    BX
  182.     POP    AX
  183.     RET
  184. CHECK_STATUS_FLAGS    ENDP
  185.  
  186.  
  187. ;-----------------------------------------------------------------------;
  188. ; This procedure reprograms the 6845 whenever a program switches modes    ;
  189. ; into an 80x25 text mode.                        ;
  190. ;-----------------------------------------------------------------------;
  191. INTERCEPT_VIDEO_IO    PROC    FAR
  192.     ASSUME    CS:CODE_SEG, DS:NOTHING
  193.     OR    AH,AH            ;Check if called for SET MODE
  194.     JZ    SET_MODE        ;It's a SET MODE call
  195.     JMP    ROM_VIDEO_IO_INT    ;Not a SET MODE, call ROM BIOS
  196. SET_MODE:
  197.     MOV    VIDEO_MODE,AL        ;Save new video mode
  198.     MOV    STATUS_LINE_ENABLED,AH    ;Disable STATLINE during mode change
  199.     PUSHF                ;Simulate INT with PUSHF, CALL
  200.     CALL    ROM_VIDEO_IO_INT    ;Let ROM BIOS change video mode
  201.     CALL    REPROGRAM_6845        ;Create 26th line again
  202.     MOV    OLD_KBD_FLAG,0        ;Flags will be clear in new mode
  203.     CALL    CHECK_STATUS_FLAGS    ;Make sure we show current flags
  204.     IRET
  205. INTERCEPT_VIDEO_IO    ENDP
  206.  
  207.  
  208.  
  209. ;-----------------------------------------------------------------------;
  210. ; The following tables describe how to reprogram the 6845 registers.    ;
  211. ; Each pair describes how to change one register.  The first number is    ;
  212. ; the register that we want to reprogram, while the second number is    ;
  213. ; the new value for that register.  Reprogram_6845 stops when it sees    ;
  214. ; a 0 for the register number.                        ;
  215. ;-----------------------------------------------------------------------;
  216. MONOCHROME_TABLE    LABEL    BYTE
  217.     DB    4,26            ;Vertical total, 26 lin